package com.appspot.yttv.client;

import com.appspot.yttv.client.JsonRequest.JsonRequestHandler;
import com.appspot.yttv.client.MediaRss.Entry;
import com.google.gwt.core.client.EntryPoint;
import com.google.gwt.core.client.JavaScriptObject;
import com.google.gwt.http.client.URL;
import com.google.gwt.user.client.Command;
import com.google.gwt.user.client.DeferredCommand;
import com.google.gwt.user.client.Timer;
import com.google.gwt.user.client.Window;
import com.google.gwt.user.client.rpc.AsyncCallback;
import com.google.gwt.user.client.ui.Button;
import com.google.gwt.user.client.ui.ChangeListener;
import com.google.gwt.user.client.ui.ClickListener;
import com.google.gwt.user.client.ui.FlowPanel;
import com.google.gwt.user.client.ui.HTML;
import com.google.gwt.user.client.ui.KeyboardListenerAdapter;
import com.google.gwt.user.client.ui.Label;
import com.google.gwt.user.client.ui.Panel;
import com.google.gwt.user.client.ui.RootPanel;
import com.google.gwt.user.client.ui.TextBox;
import com.google.gwt.user.client.ui.Widget;

/**
 * The main application
 *  
 * @author Uwe Maurer
 */
public class YouTubeTv implements EntryPoint {
	
	private final Label title = new Label();
	private final PlaylistPlayer player = new PlaylistPlayer("player1", title);
	private final  TextBox searchBox = new TextBox();


	
	private final ClickListener listenerSelect = new ClickListener() {
		public void onClick(Widget sender) {
			videoQueue.addVideo(preview.getClickedVideo());
		}
	};
	
	private final ClickListener listenerNext = new ClickListener() {
		public void onClick(Widget sender) {
			player.playVideo(videoQueue.getClickedVideo());
		}
	};

	private final PlaylistWidget videoQueue = new PlaylistWidget(listenerNext);
	private final PlaylistWidget preview = new PlaylistWidget(listenerSelect);
	private final Timer timer = new Timer() {

		@Override
		public void run() {
			  search();
		}
		
	};

	public void onModuleLoad() {
		Panel p = new FlowPanel();
		p.add(player);
	
		RootPanel.get().add(p, 269, 69);
		
		title.setStyleName("title");
		RootPanel.get().add(title, 269, 9);
		RootPanel.get().add(videoQueue,840,60);
		
		RootPanel.get().add(new HTML("<b style='color:white;'>Search</b>"));
		RootPanel.get().add(searchBox);
		
		searchBox.addKeyboardListener(new KeyboardListenerAdapter() {

			@Override
			public void onKeyUp(Widget sender, char keyCode, int modifiers) {
				if (keyCode != KEY_ENTER) {
					timer.schedule(300);
				}
			}

			@Override
			public void onKeyPress(Widget sender, char keyCode, int modifiers) {
				if (keyCode == KEY_ENTER) {
					timer.cancel();
					 search();
					 searchBox.setFocus(false);
				} 
			}
		});
		
		Button b = new Button("Next");
		RootPanel.get().add(b);
		b.addClickListener(new ClickListener() {

			public void onClick(Widget sender) {
				player.playNext();
			}
		});
		
		DeferredCommand.addCommand(new Command() {

			public void execute() {
				//String feed = "/users/uwemaurer/uploads";
				// String feed = "/standardfeeds/recently_featured";
				String feed ="/standardfeeds/most_viewed?time=today&max-results=5";
				startFeed(feed);
			}
		});
		
		RootPanel.get().add(preview);
		
		player.addChangeListener(new ChangeListener() {

			public void onChange(Widget sender) {
				preview.highlightVideo(player.getCurrentVideo());
				videoQueue.highlightVideo(player.getCurrentVideo());
			}
		});
	}
	
	public void doSearch(String query,  final AsyncCallback<Playlist> callback) {
		getFeed("/videos?racy=include&max-results=10&vq=" + URL.encodeComponent(query), callback);
    }
	
	
	public void startFeed(String feed) {
		getFeed(feed, new AsyncCallback<Playlist>() {
			
			public void onSuccess(Playlist playlist) {
			 
			  if (videoQueue.getPlaylist() == null) {
				  videoQueue.setPlaylist(playlist);
				  player.setPlaylist(playlist);
			  }
			}

			public void onFailure(Throwable caught) {
			}			
			
		});
	}
	
	public void getFeed(String feed, final AsyncCallback<Playlist> callback) {
		
		JsonRequest.get("http://gdata.youtube.com/feeds/api" + feed + "&alt=json-in-script&callback=",
				new JsonRequestHandler() {

					public void onRequestComplete(JavaScriptObject json) {
						MediaRss rss = json.cast();
						Playlist playlist = new Playlist();
						
						for (int i = 0, length = rss.getEntryLength(); i< length;  i++) {
							Entry entry = rss.getEntry(i)	;
							playlist.addVideo(new Video(entry.getId(), entry.getTitle(), entry.getChannel()));	
						}
						callback.onSuccess(playlist);
					}
			});	
	}

	private void search() {
		doSearch(searchBox.getText(), new AsyncCallback<Playlist>() {
				
				public void onSuccess(Playlist playlist) {
					preview.setPlaylist(playlist);
					preview.highlightVideo(player.getCurrentVideo());
				}

				public void onFailure(Throwable caught) {
				}			
				
			});
		
	}
}
